// src/utils/request.ts
import axios, {
  type AxiosInstance,
  type AxiosRequestConfig,
  type AxiosResponse,
  type InternalAxiosRequestConfig,
} from "axios";
import { ElMessage, ElMessageBox } from "element-plus";
import router from "@/router";

// 创建axios实例
const service: AxiosInstance = axios.create({
  baseURL: "http://localhost:8080", // 从环境变量获取
  timeout: 15000, // 超时时间
  headers: { "Content-Type": "application/json;charset=utf-8" },
});

// 请求队列（用于防止重复请求）
const pendingRequests = new Map<string, AbortController>();

// 生成请求标识
function generateReqKey(config: AxiosRequestConfig): string {
  return [
    config.method,
    config.url,
    JSON.stringify(config.params),
    JSON.stringify(config.data),
  ].join("&");
}

// 请求拦截器
service.interceptors.request.use(
  (config: InternalAxiosRequestConfig) => {

    // 自动携带token
    if (localStorage.userId && config.headers) {
      config.headers.Authorization = `Bearer ${localStorage.userId}`;
      config.headers.userId = localStorage.userId; // 根据实际token字段调整
    }

    // // 防止重复请求
    // const requestKey = generateReqKey(config);
    // if (pendingRequests.has(requestKey)) {
    //   const controller = pendingRequests.get(requestKey);
    //   controller?.abort();
    // }
    // const controller = new AbortController();
    // config.signal = controller.signal;
    // pendingRequests.set(requestKey, controller);

    // 序列化处理数组等特殊参数
    if (config.params) {
      config.paramsSerializer = (params) => {
        return Object.keys(params)
          .map((key) => {
            if (Array.isArray(params[key])) {
              return params[key].map((v: string) => `${key}=${v}`).join("&");
            }
            return `${key}=${params[key]}`;
          })
          .join("&");
      };
    }

    return config;
  },
  (error) => {
    return Promise.reject(error);
  }
);

// 响应拦截器
service.interceptors.response.use(
  (response: AxiosResponse) => {
    // 移除pending请求
    const requestKey = generateReqKey(response.config);
    pendingRequests.delete(requestKey);

    // 处理二进制数据
    if (response.request.responseType === "blob") {
      return response.data;
    }

    const res = response.data;

    // 根据业务状态码处理
    if (res.code !== 200) {
      // token过期特殊处理
      if (res.code === 401) {
        handleUnauthorized();
        return Promise.reject(new Error(res.data || "Error"));
      }

      // 其他错误状态处理
      ElMessage.error(res.data || "Error");
      return Promise.reject(new Error(res.data || "Error"));
    }

    return res;
  },
  (error) => {
    // 网络错误处理
    if (!window.navigator.onLine) {
      ElMessage.error("网络连接不可用，请检查网络设置");
      return Promise.reject(new Error("网络连接不可用"));
    }

    // 超时处理
    if (error.code === "ECONNABORTED") {
      ElMessage.error("请求超时，请重试");
      return Promise.reject(error);
    }

    // HTTP状态码处理
    if (error.response) {
      switch (error.response.status) {
        case 401:
          handleUnauthorized();
          break;
        case 403:
          router.push("/403");
          break;
        case 404:
          ElMessage.error("请求资源不存在");
          break;
        case 500:
          ElMessage.error("服务器内部错误");
          break;
        default:
          ElMessage.error(error.response.data.message || "请求失败");
      }
    }

    return Promise.reject(error);
  }
);

// 处理401未授权
function handleUnauthorized() {

  ElMessageBox.confirm("登录状态已过期，请重新登录", "提示", {
    confirmButtonText: "重新登录",
    cancelButtonText: "取消",
    type: "warning",
  })
    .then(() => {
      router.replace({
        path: "/login",
        query: {
          redirect: router.currentRoute.value.fullPath,
        },
      });
    })
    .catch(() => {
      // 取消操作
    });
}

export default service;
